import json
import re

from QQLoginTool.QQtool import OAuthQQ
from django.conf import settings
from django.contrib.auth import login
from django.http import JsonResponse
from django.shortcuts import render
import logging

from django_redis import get_redis_connection

from oauth.models import OAuthQQUser
from oauth.utils import get_access_token_by_openid, get_openid
from users.models import User

logger = logging.getLogger('django')

# Create your views here.
from django.views import View


class QQFirstView(View):
    def get(self, request):
        # next记录的是一个网址,比如你点击用户中心,但你没登录就会把用户中心地址记录,
        # 然后跳转到登录界面,登录成功后就会转到用户中心,而不是首页
        next = request.GET.get('next')

        # 获取 QQ 登录页面网址
        # 创建 OAuthQQ 类的对象
        oauth = OAuthQQ(client_id=settings.QQ_CLIENT_ID,
                        client_secret=settings.QQ_CLIENT_SECRET,
                        redirect_uri=settings.QQ_REDIRECT_URI,
                        state=next)
        # 调用对象.get_qq_url()方法获取qq地址
        login_url = oauth.get_qq_url()

        # 返回登录地址
        return JsonResponse({'code': 0,
                             'errmsg': 'OK',
                             'login_url': login_url})


class QQUserView(View):
    """用户扫码登录的回调处理"""

    def get(self, request):
        """Oauth2.0认证"""
        # 获取前端发送过来的 code 参数:
        code = request.GET.get('code')

        if not code:
            # 判断 code 参数是否存在
            return JsonResponse({'code': 400,
                                 'errmsg': '缺少code参数'})

        # 调用我们安装的 QQLoginTool 工具类
        # 创建工具对象
        oauth = OAuthQQ(client_id=settings.QQ_CLIENT_ID,
                        client_secret=settings.QQ_CLIENT_SECRET,
                        redirect_uri=settings.QQ_REDIRECT_URI)

        try:
            # 携带 code 向 QQ服务器 请求 access_token
            access_token = oauth.get_access_token(code)

            # 携带 access_token 向 QQ服务器 请求 openid
            openid = oauth.get_open_id(access_token)

        except Exception as e:
            # 如果上面获取 openid 出错, 则验证失败
            logger.error(e)
            # 返回结果
            return JsonResponse({'code': 400,
                                 'errmsg': 'oauth2.0认证失败, 即获取qq信息失败'})
        try:
            oauth_obj = OAuthQQUser.objects.get(openid=openid)
        except Exception as e:
            access_token=get_access_token_by_openid(openid)

            return JsonResponse({'code': 300,
                                 'errmsg': 'ok',
                                 'access_token':access_token})
        else:
            user = oauth_obj.user

            login(request, user)

            response = JsonResponse({'code': 0,
                                     'errmsg': 'ok',
                                     })
            response.set_cookie('username',
                                user.username,
                                max_age=3600 * 24 * 14)
            return response

    def post(self,request):
        dict=json.loads(request.body.decode())
        mobile=dict.get('mobile')
        password=dict.get('password')
        sms_code_client=dict.get('sms_code')
        access_token=dict.get('access_token')
        if not all([mobile,password,sms_code_client,access_token]):
            return JsonResponse({'code':400,
                                 'errmsg':'缺少必传参数'})
        # 判断手机号是否合法
        if not re.match(r'^1[3-9]\d{9}$', mobile):
            return JsonResponse({'code': 400,
                                 'errmsg': '请输入正确的手机号码'})

        # 判断密码是否合格
        if not re.match(r'^[0-9A-Za-z]{8,20}$', password):
            return JsonResponse({'code': 400,
                                 'errmsg': '请输入8-20位的密码'})
        redis_conn=get_redis_connection('verify_code')

        sms_code_server=redis_conn.get(mobile).decode()

        if sms_code_server is None:
            return JsonResponse({'code':400,
                                 'errmsg':'验证码失效'})
        if sms_code_server != sms_code_client:
            return JsonResponse({'code':400,
                                 'errmsg':'验证码错误'})
        openid=get_openid(access_token)

        if not openid:
            return JsonResponse({'code':400,
                                 'errmsg':'获取openid失败'})
        try:
            user=User.objects.get(mobile=mobile)
        except Exception as e:
            user=User.objects.create_user(username=mobile,
                                          mobile=mobile,
                                          password=password)
        else:
            if not user.check_password(password):
                return JsonResponse({'code':400,
                                     'errmsg':'密码错误'})
        try:
            OAuthQQUser.objects.create(openid=openid,
                                       user=user)
        except Exception as e:
            return JsonResponse({'code': 400,
                                 'errmsg': '往数据库添加数据出错'})
        login(request,user)

        response=JsonResponse({'code':0,
                               'errmsg':'ok'})
        response.set_cookie('username',
                            user.username,
                            max_age=3600*24*14)
        return response